package com.seirsoft.cookingtime.ui.controls;

import java.util.List;

import org.eclipse.jface.viewers.IStructuredContentProvider;
import org.eclipse.jface.viewers.StructuredSelection;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.jface.viewers.Viewer;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.TableEditor;
import org.eclipse.swt.events.ControlAdapter;
import org.eclipse.swt.events.ControlEvent;
import org.eclipse.swt.events.ControlListener;
import org.eclipse.swt.events.FocusEvent;
import org.eclipse.swt.events.FocusListener;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.MouseEvent;
import org.eclipse.swt.events.MouseListener;
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Layout;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Table;
import org.eclipse.swt.widgets.TableColumn;
import org.eclipse.swt.widgets.TableItem;
import org.eclipse.swt.widgets.Text;

import com.seirsoft.cookingtime.internal.IViewTable;
import com.seirsoft.cookingtime.internal.IViewTableCallback;
import com.seirsoft.cookingtime.model.TimeElement;
import com.seirsoft.framework.util.GUIUtil;

public class sierTableViewer extends TableViewer 
implements MouseListener, IViewTable, FocusListener
{

	IViewTableCallback m_viewTable = null;

	public sierTableViewer(Composite parent, int style) {
		super(parent, style);

		Table table = this.getTable();
		table.addMouseListener(this);
		table.addFocusListener(this);
		this.setContentProvider(new ContentProvider());
	}


	public void AddSelectionListener(IViewTableCallback viewTable) {
		m_viewTable = viewTable;
	}

	public class ContentProvider implements IStructuredContentProvider {

		@Override
		public Object[] getElements(Object object) {
			if (object instanceof List) {
				return ((List<?>) object).toArray();
			}
			return null;
		}

		@Override
		public void dispose() {
			// TODO Auto-generated method stub

		}

		@Override
		public void inputChanged(Viewer arg0, Object arg1, Object arg2) {
			// TODO Auto-generated method stub

		}

	}

	private static class TableLayout extends Layout {
		@Override
		protected Point computeSize(Composite composite, int wHint, int hHint,
				boolean flushCache) {
			composite.setLayout(null);
			Point size = composite.computeSize(wHint, hHint, flushCache);
			composite.setLayout(this);
			return size;
		}

		@Override
		protected void layout(Composite composite, boolean flushCache) {
			Rectangle clientArea = composite.getClientArea();
			Table table = (Table) composite;
			TableColumn columns[] = table.getColumns();
			int totalColumnWidth = 0;
			for (int i = 0; i < columns.length; i++)
				totalColumnWidth += columns[i].getWidth();

			table.setLayout(null);
			if (totalColumnWidth < clientArea.width) {
				TableColumn lastColumn = columns[columns.length - 1];
				int lastColumnWidth = lastColumn.getWidth();
				lastColumnWidth += clientArea.width - totalColumnWidth;
				lastColumn.setWidth(lastColumnWidth);
			} else if (totalColumnWidth > clientArea.width) {
				TableColumn lastColumn = columns[columns.length - 1];
				int lastColumnWidth = lastColumn.getWidth();
				int otherColumnWidths = totalColumnWidth - lastColumnWidth;
				int newWidth = clientArea.width - otherColumnWidths;
				if (newWidth < 15)
					newWidth = 15;
				lastColumn.setWidth(newWidth);
				
			}
			
			int height = table.getHeaderHeight();

			int totalRowHeight = 0;
			TableItem[] items = table.getItems();
			for (int j = 0; j < items.length; j++)
				totalRowHeight += items[j].getBounds().height;

			
//			Label lb = new Label(table, SWT.None);
//			lb.setText("wefwefwef");
//			lb.setBounds(table.getLocation().x, table.getLocation().y + height+totalRowHeight, totalColumnWidth, table.getItemHeight());

			table.setLayout(this);
		}
	}

	@Override
	public void mouseDoubleClick(MouseEvent e) {
		Table table = this.getTable();
		if (m_viewTable == null || table == null)
			return;

		Point pt = new Point(e.x, e.y);
		int iItemCount = table.getItemCount();
		int iColumnCount = table.getColumnCount();

		for (int iRowIndex = 0; iRowIndex < iItemCount; iRowIndex++) {
			TableItem item = table.getItem(iRowIndex);

			for (int j = 0; j < iColumnCount; j++) {
				if (item.getBounds(j).contains(pt)) {
					m_viewTable.fireEventCellDoubleClick(true, iRowIndex, j);
					return;
				}
			}
		}
		m_viewTable.fireEventCellDoubleClick(false, -1, -1);
	}

	@Override
	public void mouseDown(MouseEvent e) {

	}

	@Override
	public void mouseUp(MouseEvent e) {
		Table table = this.getTable();
		if (m_viewTable == null || table == null)
			return;

		Point pt = new Point(e.x, e.y);
		int iItemCount = table.getItemCount();
		int iColumnCount = table.getColumnCount();

		Rectangle rect = table.getBounds();
		rect.x=0;
		rect.y=0;

		if (rect.contains(pt)) {
			for (int iRowIndex = 0; iRowIndex < iItemCount; iRowIndex++) {
				TableItem item = table.getItem(iRowIndex);

				Rectangle re = item.getBounds();
				for (int j = 0; j < iColumnCount; j++) {
					if (item.getBounds(j).contains(pt)) {
						m_viewTable.fireEventCellClick(true, iRowIndex, j);
						return;
					}
				}

			}
		}
		m_viewTable.fireEventCellClick(false, -1, -1);
	}

	private TableEditor m_editor = null;

	
	
	@Override
	public void EditCell(final int iRow, final int iColumn) {
		Table table = this.getTable();
		
		TableItem item = table.getItem(iRow);

		if (m_editor == null)
			m_editor = new TableEditor(table);

		Control ctl = m_editor.getEditor();
		if (ctl != null)
			ctl.dispose();

		m_editor.grabHorizontal = true;
		
		final Text text = new Text(table, SWT.NONE);
		GridData data = new GridData(GridData.FILL_BOTH);
		text.setLayoutData(data);
		text.addModifyListener(new ModifyListener(){

			@Override
			public void modifyText(ModifyEvent e) {
				if(m_viewTable != null)
					m_viewTable.fireEventCellTextChanged(iRow, iColumn, text.getText());
			}
			
		});
		
	    Font font = new Font (table.getDisplay(), "����", 15, SWT.BORDER); 
	    text.setFont(font);
	    
		text.addListener(SWT.MeasureItem, new Listener() {
            public void handleEvent(Event event)
            {
                event.height = event.gc.getFontMetrics().getHeight() + 4;
            }
        });
		
		//text.addFocusListener(this);
		
		text.setFocus();
		m_editor.setEditor(text, item, iColumn);
	}
	
	@Override
	public String GetCellValue(int iRow, int iColumn)
	{
		Table table = this.getTable();
		TableItem item = table.getItem(iRow);
		return item.getText(iColumn);
	}
	
	@Override
	public void SetViewMode()
	{
		if (m_editor == null)
			return;

		Control ctl = m_editor.getEditor();
		if (ctl != null)
			ctl.dispose();
	}

	@Override
	public void focusGained(FocusEvent e) {
		// TODO Auto-generated method stub
		
	}

	@Override
	public void focusLost(FocusEvent e) {
		if(this.m_viewTable != null)
			this.m_viewTable.fireEventFocusLost();
	}

	@Override
	public void RefreshTable() {
		this.refresh();
	}

	@Override
	public void SetInput(Object input) {
		super.setInput(input);
		super.getTable().layout(true);
	}

	@Override
	public void SetSelection(Object input) {
		if(input != null)
		{
			StructuredSelection selection = new StructuredSelection(input);
			super.setSelection(selection);
		}
		else
			super.setSelection(null);
	}

	@Override
	public void setTableHeaders(String[] aryHeaders, int[] width) {
		Table table = this.getTable();
		table.setLayout(new TableLayout());
		
		ControlListener layoutWhenResizedListener = new ControlAdapter() {

			public void controlResized(ControlEvent e) {
				((TableColumn) e.widget).getParent().layout();
			}
		};

		int iColumnCount = aryHeaders.length;
		for (int i = 0; i < iColumnCount; i++) {
			TableColumn column = new TableColumn(table, SWT.LEFT);

			column.setText(aryHeaders[i]);
			column.setWidth(width[i]);
			column.addControlListener(layoutWhenResizedListener);
		}

	}

	@Override
	public void updateRow(int row, TimeElement objTimeElement) {
		this.update(objTimeElement, null);
	}
}
